package com.bingxue.edu.management.system.service;

import com.bingxue.edu.framework.mybatis.base.BaseService;
import com.bingxue.edu.management.system.mapper.ResourceMapper;
import com.bingxue.edu.management.system.mapper.RoleResourceMapper;
import com.bingxue.edu.management.system.model.entity.RoleResource;
import com.bingxue.edu.management.system.model.req.RoleResourceUpdateReq;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

import static com.bingxue.edu.common.constant.AuthConstants.SUPER_ADMIN_ROLE_ID;
import static com.bingxue.edu.management.system.model.entity.table.ResourceTableDef.RESOURCE;
import static com.bingxue.edu.management.system.model.entity.table.RoleResourceTableDef.ROLE_RESOURCE;
import static com.mybatisflex.core.query.QueryMethods.distinct;

/**
 * 角色-资源业务实现类
 *
 * @author panbo
 * @since 2024/08/21 13:18
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class RoleResourceService extends BaseService<RoleResourceMapper, RoleResource> {

    private final ResourceMapper resourceMapper;

    /**
     * 查询角色资源
     * @param roleIds 角色id列表
     * @return 资源列表
     */
    public List<String> getResourceCodeListByRoleIds(List<String> roleIds) {
        if (roleIds == null || roleIds.isEmpty()) {
            return List.of();
        }
        // 超级管理员返回所有资源
        if (roleIds.contains(SUPER_ADMIN_ROLE_ID)) {
            return List.of("*");
        }
        return this.queryChain()
                .select(distinct(RESOURCE.CODE))
                .from(ROLE_RESOURCE)
                .leftJoin(RESOURCE).on(ROLE_RESOURCE.RESOURCE_ID.eq(RESOURCE.ID))
                .where(ROLE_RESOURCE.ROLE_ID.in(roleIds))
                .listAs(String.class);
    }

    /**
     * 更新角色资源列表
     * @param req
     * @return
     */
    @Transactional(rollbackFor = Exception.class)
    public void updateRoleResource(RoleResourceUpdateReq req) {
        // 先清空
        this.updateChain().where(ROLE_RESOURCE.ROLE_ID.eq(req.getRoleId())).remove();
        // 再创建
        List<RoleResource> roleResourceList = req.getResourceList().stream().map(item -> {
            RoleResource roleResource = new RoleResource();
            roleResource.setRoleId(req.getRoleId());
            roleResource.setResourceId(item);
            return roleResource;
        }).toList();
        this.saveBatch(roleResourceList);
    }
}
